package com.bpc.cs.managed.bean;

import java.io.Serializable;
import java.util.List;

import javax.faces.context.FacesContext;
import javax.faces.event.ActionEvent;
import javax.servlet.http.HttpServletRequest;

import com.bpc.cs.constant.AttributeName;
import com.bpc.cs.constant.Constant;
import com.bpc.cs.managed.dvo.RuleDVO;
import com.bpc.cs.service.IRuleService;
import com.bpc.cs.util.Message;
import com.bpc.cs.util.Util;

/**
 * @author   phan_tp
 * @datetime Dec 3, 2012 : 11:07:28 AM
 */

public class RuleBean extends BaseBean implements Serializable {

	private static final long serialVersionUID = -3106880838568719444L;
	private IRuleService ruleService;
	private List<RuleDVO> listRule;
	private RuleDVO selectedRule;
	private int schemeID;
	private String weight;
	private boolean visibleRule = false;
	private int numOfRecCurPage = 0;

	public RuleBean() {
		super();
	}

	/**
	 * Get all rule by SchemeID
	 * @return the listRule
	 */
	public void preGetListRule() {
		// Call ruleService to get list rule of schemeID
		listRule = ruleService.getRuleBySchemeID(schemeID);

		// Clone and put list rule of schemeID to session
		getSession().setAttribute(AttributeName.LIST_RULE, Util.cloneListRuleDVO(listRule));

		// Set size of current list in current page
		numOfRecCurPage = (listRule.size() >= 10) ? 10 : listRule.size();
	}

	/**
	 * Get factor choice by ruleID
	 * @param ActionEvent event
	 */
	public void getFactorChoice(ActionEvent event) {
		FactorChoiceBean facChoBean = (FactorChoiceBean)getBean(Constant.FACTOR_CHOICE_BEAN, FactorChoiceBean.class);
		// Set get RuleID prepare for method getListFactorChoice()
		facChoBean.preGetListFactorChoice();
		facChoBean.setSelectedFactorChoice(null);
	}

	/**
	 * Load data for form add rule
	 * @param ActionEvent event
	 */
	public void viewFormAddRule(ActionEvent event) {
		FactorBean factorBean = (FactorBean)getBean(Constant.FACTOR_BEAN, FactorBean.class);
		factorBean.preGetListFactor();
		factorBean.setSelectedFactor(0);
		setWeight(null);
		getSession().setAttribute(AttributeName.IS_EDIT_RULE, false);
	}

	/**
	 * Load data for form edit rule
	 * @param ActionEvent event
	 */
	public void viewFormEditRule(ActionEvent event) {
		FactorBean factorBean = (FactorBean)getBean(Constant.FACTOR_BEAN, FactorBean.class);
		factorBean.preGetListFactor();
		factorBean.setSelectedFactor(selectedRule.getFactorID());
		setWeight(String.valueOf(selectedRule.getWeight()));
		getSession().setAttribute(AttributeName.IS_EDIT_RULE, true);
	}

	/**
	 * Remove rule
	 * @param ActionEvent event
	 */
	public void removeRule(ActionEvent event) {
		if (ruleService.removeRule(selectedRule.getRuleID())) {
			preGetListRule();
			selectedRule = null;
		} else {
			HttpServletRequest request = (HttpServletRequest)FacesContext.getCurrentInstance()
																		 .getExternalContext()
																		 .getRequest();
			request.setAttribute(AttributeName.SHOW_MSG_RULE_HAS_FACTORCHOICE, true);
		}
	}

	/**
	 * Remove rule and factor choice
	 * @param ActionEvent event
	 */
	public void removeEntireRule(ActionEvent event) {
		ruleService.removeEntireRule(selectedRule.getRuleID());
		preGetListRule();
		selectedRule = null;
	}

	/**
	 * Add new rule or update rule for scheme
	 * @param ActionEvent event
	 */
	@SuppressWarnings("unchecked")
	public void saveRule(ActionEvent event) {
		FactorBean factorBean = (FactorBean)getBean(Constant.FACTOR_BEAN, FactorBean.class);
		SchemeBean schemeBean = (SchemeBean)getBean(Constant.SCHEME_BEAN, SchemeBean.class);

		// Check action which is Edit rule or Add new rule
		if (Boolean.parseBoolean(getSession().getAttribute(AttributeName.IS_EDIT_RULE).toString())) {
			// Get list rule of scheme in session - List isn't updated by user
			List<RuleDVO> listRuleOfSess = (List<RuleDVO>)getSession().getAttribute(AttributeName.LIST_RULE);

			// Edit Rule
			Message msg = ruleService.editRule(selectedRule,
											   schemeBean.getSelectedScheme(),
											   factorBean.getSelectedFactor(factorBean.getSelectedFactor()),
											   Float.parseFloat(weight),
											   listRuleOfSess);

			// Check result of service
			if (msg.isResultBoolean()) {
				// Get list rule of schemeID again after edit rule
				preGetListRule();

				// Reset some field to original value
				visibleRule = true;
				factorBean.setSelectedFactor(listRule.get(0).getFactorID());
				weight = null;
			}

			// Set value for message key to decide show message or not
			getRequest().setAttribute(msg.getMessageKey(), !msg.isResultBoolean());
		} else {
			// Add new rule
			// Call ruleService to execute add new ruel for schemeID
			Message msg = ruleService.addRule(schemeBean.getSelectedScheme(),
											  factorBean.getSelectedFactor(factorBean.getSelectedFactor()),
											  Float.parseFloat(weight));

			// Check return value of service
			if (msg.isResultBoolean()) {
				// Get list rule of schemeID again after add new rule
				preGetListRule();

				// Reset primity data of
				visibleRule = true;
				factorBean.setSelectedFactor(listRule.get(0).getFactorID());
				weight = null;
			}

			// Set value for message key to decide show message or not
			getRequest().setAttribute(msg.getMessageKey(), !msg.isResultBoolean());
		}
	}

	/**
	 * Get all rule by SchemeID
	 * @return the listRule
	 */
	public List<RuleDVO> getListRule() {
		return listRule;
	}

	/**
	 * @param List<RuleDVO> listRule
	 */
	public void setListRule(List<RuleDVO> listRule) {
		this.listRule = listRule;
	}

	/**
	 * Set SchemeID
	 * @param int schemeID
	 */
	public void setSchemeID(int schemeID) {
		this.schemeID = schemeID;
	}

	/**
	 * @return the ruleService
	 */
	public IRuleService getRuleService() {
		return ruleService;
	}

	/**
	 * @param ruleService the ruleService to set
	 */
	public void setRuleService(IRuleService ruleService) {
		this.ruleService = ruleService;
	}

	/**
	 * @return the selectedRule
	 */
	public RuleDVO getSelectedRule() {
		return selectedRule;
	}

	/**
	 * @param selectedRule the selectedRule to set
	 */
	public void setSelectedRule(RuleDVO selectedRule) {
		this.selectedRule = selectedRule;
	}

	/**
	 * @return the weight
	 */
	public String getWeight() {
		return weight;
	}

	/**
	 * @param weight the weight to set
	 */
	public void setWeight(String weight) {
		this.weight = weight;
	}

	/**
	 * @return the visibleRule
	 */
	public boolean isVisibleRule() {
		return visibleRule;
	}

	/**
	 * @param visibleRule the visibleRule to set
	 */
	public void setVisibleRule(boolean visibleRule) {
		this.visibleRule = visibleRule;
	}

	/**
	 * @return the numOfRecCurPage
	 */
	public int getNumOfRecCurPage() {
		return numOfRecCurPage;
	}

	/**
	 * @param numOfRecCurPage the numOfRecCurPage to set
	 */
	public void setNumOfRecCurPage(int numOfRecCurPage) {
		this.numOfRecCurPage = numOfRecCurPage;
	}

}